/*
* Copyright (c) 2007 by Kirill Kolodyazhniy.
* See the file "license.terms" for information on usage and redistribution.
*/

#ifndef M_COLOR_H
#define M_COLOR_H

namespace Engine
{
    typedef unsigned int RGBA;
    typedef unsigned int ARGB;
    typedef unsigned int ABGR;

    /**
	*   Class representing color.
	*/
    class Color
    {
    public:
	    static Color Black;
	    static Color White;
	    static Color Red;
	    static Color Green;
	    static Color Blue;
		/**********************************************************************************************************/
	    Color( float red = 1.0f,
				    float green = 1.0f,
				    float blue = 1.0f,
					float alpha = 1.0f )
        {
			r=red;
			g=green;
			b=blue;
			a=alpha;
		}
		/**********************************************************************************************************/
	    bool operator==(const Color& rhs) const;
		/**********************************************************************************************************/
	    bool operator!=(const Color& rhs) const;
		/**********************************************************************************************************/
        float r,g,b,a;
		/**********************************************************************************************************/
        inline operator unsigned int () const
        {
            return GetAsARGB();
        }
		/**********************************************************************************************************/
        inline operator float* ()
        {
            return  &r;
        }
		/**********************************************************************************************************/
        inline operator const float* () const
        {
            return const_cast<const float *>( &r);
        }
		/**********************************************************************************************************/
	    RGBA GetAsRGBA(void) const;
		/**********************************************************************************************************/
		ARGB GetAsARGB(void) const;
		/**********************************************************************************************************/
		ABGR GetAsABGR(void) const;
		/**********************************************************************************************************/
		inline Color operator + ( const Color& rhs ) const
        {
            Color kSum;

            kSum.r = r + rhs.r;
            kSum.g = g + rhs.g;
            kSum.b = b + rhs.b;
            kSum.a = a + rhs.a;

            return kSum;
        }
		/**********************************************************************************************************/
        inline Color operator - ( const Color& rhs ) const
        {
            Color kDiff;

            kDiff.r = r - rhs.r;
            kDiff.g = g - rhs.g;
            kDiff.b = b - rhs.b;
            kDiff.a = a - rhs.a;

            return kDiff;
        }
		/**********************************************************************************************************/
        inline Color operator * ( float fScalar ) const
        {
            Color kProd;

            kProd.r = fScalar*r;
            kProd.g = fScalar*g;
            kProd.b = fScalar*b;
            kProd.a = fScalar*a;

            return kProd;
        }
		/**********************************************************************************************************/
        inline Color operator * ( const Color& rhs) const
        {
            Color kProd;

            kProd.r = rhs.r * r;
            kProd.g = rhs.g * g;
            kProd.b = rhs.b * b;
            kProd.a = rhs.a * a;

            return kProd;
        }
		/**********************************************************************************************************/
        inline Color operator / ( const Color& rhs) const
        {
            Color kProd;

            kProd.r = rhs.r / r;
            kProd.g = rhs.g / g;
            kProd.b = rhs.b / b;
            kProd.a = rhs.a / a;

            return kProd;
        }
		/**********************************************************************************************************/
        inline Color operator / ( float fScalar ) const
        {


            Color kDiv;

            float fInv = 1.0f / fScalar;
            kDiv.r = r * fInv;
            kDiv.g = g * fInv;
            kDiv.b = b * fInv;
            kDiv.a = a * fInv;

            return kDiv;
        }
		/**********************************************************************************************************/
        inline friend Color operator * ( float fScalar, const Color& rhs )
        {
            Color kProd;

            kProd.r = fScalar * rhs.r;
            kProd.g = fScalar * rhs.g;
            kProd.b = fScalar * rhs.b;
            kProd.a = fScalar * rhs.a;

            return kProd;
        }
		/**********************************************************************************************************/
		inline Color& operator += ( const Color& rhs )
        {
            r += rhs.r;
            g += rhs.g;
            b += rhs.b;
            a += rhs.a;

            return *this;
        }
		/**********************************************************************************************************/
        inline Color& operator -= ( const Color& rhs )
        {
            r -= rhs.r;
            g -= rhs.g;
            b -= rhs.b;
            a -= rhs.a;

            return *this;
        }
		/**********************************************************************************************************/
        inline Color& operator *= ( float fScalar )
        {
            r *= fScalar;
            g *= fScalar;
            b *= fScalar;
            a *= fScalar;
            return *this;
        }
		/**********************************************************************************************************/
        inline Color& operator /= ( float fScalar )
        {


            float fInv = 1.0f / fScalar;

            r *= fInv;
            g *= fInv;
            b *= fInv;
            a *= fInv;

            return *this;
        }
		/**********************************************************************************************************/
    };
}

#endif
